package gameframe;

import client.ClientPlayer;
import gamelobby.GameLobby;
import musicthread.MusicThread;

import javax.swing.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

/**
 * @author Hsu琛君珩
 * @ClassName:GameFrame
 * @date 2023-12-20
 * @apiNote
 * @Version: v1.0
 */

/**
 * 游戏主窗口类。
 * 用于显示和管理五子棋游戏的主界面。
 */
public class GameFrame extends JFrame {

    /**
     * 游戏主窗口类的单例实例。
     * 这个静态变量持有类的唯一实例。单例模式确保整个应用程序中只创建一个GameFrame实例。
     */
    private static GameFrame instance;
    /**
     * 游戏中的棋盘面板。
     * 这个面板负责显示棋盘和棋子，并处理与棋局相关的用户交互。
     */
    private static ChessPanel chessPanel;
    /**
     * 游戏中的聊天面板。
     * 这个面板显示聊天信息，并允许用户发送消息，还可能包含其他控制元素，如悔棋和认输按钮。
     */
    private static ChatPanel chatPanel;
    /**
     * 游戏窗口的菜单栏。
     * 这个菜单栏可以包含多个菜单项，用于执行各种游戏相关的操作，如返回游戏大厅、保存游戏等。
     */
    private static JMenuBar menuBar;
    /**
     * 菜单栏中的一个菜单。
     * 这个特定的菜单可能包含多个与游戏操作相关的菜单项。
     */
    private static JMenu menu;
    /**
     * 一个菜单项。
     * 这个菜单项允许用户执行特定的操作，如返回游戏大厅。点击此菜单项将触发相关的事件处理程序。
     */
    private static JMenuItem returnMenu;

    /**
     * 获取GameFrame的单例实例。
     * 如果实例不存在，则创建一个新实例。
     *
     * @return GameFrame的单例实例
     */
    public static GameFrame getInstance() {
        if (instance == null) {
            instance = new GameFrame();
        }
        return instance;
    }

    /**
     * 构造方法，初始化游戏窗口。
     * 由于这是一个私有构造方法，它只能在本类内部被调用，这是实现单例模式的一部分。
     */
    private GameFrame() {
        // 设置窗口的初始位置和大小。
        this.setBounds(300, 100, 710, 480);
        // 设置窗口不可通过拖动边缘来调整大小。
        this.setResizable(false);
        // 设置默认的关闭操作。当用户点击窗口的关闭按钮时，应用程序将停止执行。
        this.setDefaultCloseOperation(EXIT_ON_CLOSE);
        // 创建菜单栏，并添加一个名为"操作"的菜单。
        menuBar = new JMenuBar();
        menu = new JMenu("操作");
        // 在菜单中添加一个名为"返回游戏大厅"的菜单项。
        returnMenu = new JMenuItem("崩撤卖溜");
        menu.add(returnMenu);
        menuBar.add(menu);
        // 将菜单栏设置到游戏窗口中。
        this.setJMenuBar(menuBar);
        // 初始化窗口的事件监听器，这通常涉及到响应用户的操作，如点击菜单项。
        initActionListener();
        // 创建并初始化棋盘面板和聊天面板，它们是游戏界面的主要组成部分。
        chessPanel = ChessPanel.getInstance();
        chatPanel = ChatPanel.getInstance();
        // 将棋盘面板和聊天面板添加到窗口的内容面板中，这样它们就可以在窗口中显示了。
        this.getContentPane().add(chessPanel);
        this.getContentPane().add(chatPanel);
        // 使窗口可见。在这之前，所有的组件都已经添加到窗口中，但窗口本身还不会显示。
        this.setVisible(true);
    }

    /**
     * 初始化事件监听。
     * 为菜单项添加事件处理程序。
     */
    private void initActionListener() {
        returnMenu.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                System.out.println("选择返回游戏大厅");
                ClientPlayer.getInstance().returnGameLobby();
                MusicThread.getInstance().stopBackgroundMusic(); // 停止播放背景音乐
            }
        });
    }

    /**
     * 展示胜利提示。
     */
    public void showWin() {
        JOptionPane.showMessageDialog(this, "我们是冠军！", "胜利！", JOptionPane.INFORMATION_MESSAGE);
    }

    /**
     * 展示失败提示。
     */
    public void showLose() {
        JOptionPane.showMessageDialog(this, "四强就算成功！", "失败！", JOptionPane.ERROR_MESSAGE);
    }

    /**
     * 展示游戏结束提示。
     * @param winner 获胜方
     */
    public void showGameOver(int winner) {
        String winnerColor = (winner == 1) ? "BLACK" : "WHITE";
        JOptionPane.showMessageDialog(null, "对局结束, " + winnerColor + " 获胜!", "许老师好帅！", JOptionPane.INFORMATION_MESSAGE);
    }

}
